package com.service.single.util;

import com.alibaba.fastjson.JSON;
import com.auth0.jwt.JWT;
import com.auth0.jwt.JWTVerifier;
import com.auth0.jwt.algorithms.Algorithm;
import com.auth0.jwt.interfaces.Claim;
import com.service.single.entity.SystemUser;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.time.LocalDateTime;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;

/**
 * @author admin
 */
public class TokenUtil {

    /**
     * token过期时间
     */
    private static final long EXPIRE_TIME = 30 * 60 * 1000;
    /**
     * token秘钥
     */
    private static final String TOKEN_SECRET = "token";


    /**
     * 生成签名，30分钟过期
     *
     * @return 生成的token
     */
    public static String sign(SystemUser user, LocalDateTime loginTime) {
        try {
            // 设置过期时间
            Date date = new Date(System.currentTimeMillis() + EXPIRE_TIME);
            // 私钥和加密算法
            Algorithm algorithm = Algorithm.HMAC256(TOKEN_SECRET);
            // 设置头部信息
            Map<String, Object> header = new HashMap<>(3);
            header.put("Type", "Jwt");
            header.put("alg", "HS256");
            // 返回token字符串
            return JWT.create()
                    .withHeader(header)
                    .withClaim("loginName", user.getUsername())
                    .withClaim("userId", user.getId())
                    .withClaim("loginTime", loginTime.toString())
                    .withExpiresAt(date)
                    .sign(algorithm);
        } catch (Exception e) {
            e.printStackTrace();
            return null;
        }
    }

    /**
     * 检验token是否正确
     *
     * @param token 需要校验的token
     * @return 校验是否成功
     */
    public static boolean verify(String token) {
        try {
            //设置签名的加密算法：HMAC256
            Algorithm algorithm = Algorithm.HMAC256(TOKEN_SECRET);
            JWTVerifier verifier = JWT.require(algorithm).build();
            verifier.verify(token);
            return true;
        } catch (Exception e) {
            return false;
        }
    }

    /**
     * 解析token
     */
    public static Map<String, Claim> parseJwt() {
        HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()).getRequest();
        // 获取token 并校验
        String token = request.getHeader("Authorization").replace("Bearer ", "");
        return JWT.decode(token).getClaims();
    }

    public static void main(String[] args) {
        String token = "eyJhbGciOiJIUzI1NiIsIlR5cGUiOiJKd3QiLCJ0eXAiOiJKV1QifQ.eyJsb2dpblRpbWUiOiIyMDIxLTA3LTE0VDE1OjA0OjAwLjA2MSIsImxvZ2luTmFtZSI6IuW8oOS4iSIsImV4cCI6MTYyNjI0OTg0MH0.xXoq2LJOagyYo7rBAa_CJIE0NJQg3DjYqa7pxlcOOdo";
        // 解析当前登录人的名称
        Map<String, Claim> map = JWT.decode(token).getClaims();
        System.out.println(JSON.toJSONString(map));
        System.out.println(map.get("loginName").asString());
        HttpServletResponse response = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()).getResponse();

    }

}
